import _ from 'lodash'
import { ipcMain, Event } from 'electron'
import mysql from 'mysql';
import IElectronModule from './bg_base';
import { IpcConnnectionBase } from '@/plugin/ipc_renderer_ex';
import { ConnectionConfig } from 'mysql';

/** 连接 mysql 数据库 */
export const MYSQL_CONN = "mysql-conn";
const MYSQL_CONN_RET = "mysql-conn-ret";
/** mysql 的查询操作 */
export const MYSQL_QUERY = "mysql-query";
const MYSQL_QUERY_RET = "mysql-query-ret";

// 定义ipc接口
declare module '@/plugin/ipc_renderer_ex' {
    interface IpcSendTypes {
        [MYSQL_CONN]: IpcSendTypeNode<IpcConnnectionMysql, IpcReturnDBKey>
        [MYSQL_QUERY]: IpcSendTypeNode<IpcConnnectionGetByPath, IpcReturnValue<any>>
    }
}

/** 通过网络数据库信息连接 MySQL */
export interface IpcConnnectionMysql extends IpcConnnectionBase, ConnectionConfig {
}

class MysqlConn implements IElectronModule {

    private static _connection_map: Map<string, mysql.Connection> = new Map<string, mysql.Connection>();

    install(): void {
        ipcMain.on(MYSQL_CONN, this.mysqlConnection.bind(this));
        ipcMain.on(MYSQL_QUERY, this.mysqlQuery.bind(this));
        ipcMain.on("mysql-close", this.mysqlClose.bind(this));
    }

    /**
     * 连接数据库
     * @param event 事件信息
     * @param param1.key 连接的识别关键字 
     */
    private mysqlConnection(
        event: Event,
        {
            key = "", host = "", user = "", password = "", database = ""
        }: {
            key: string, host: string, user: string, password: string, database: string
        }
    ): void {
        let conn_key = _.isEmpty(key) ? "conn_" + _.random(0, 99999) : key;
        let conn = mysql.createConnection({
            host, user, password, database,
            multipleStatements: true
        });
        MysqlConn._connection_map.set(conn_key, conn);
        event.returnValue = conn_key;
    }

    /**
     * 数据库查询
     * @param event  事件信息
     * @param param1 
     */
    private mysqlQuery(
        event: Event,
        { key = "", statement = "", values = null }: { key: string, statement: string, values: Object | null }
    ) {
        let connection = MysqlConn._connection_map.get(key);
        if (!_.isNil(connection)) {

            if (connection.state == "disconnected") {
                connection.connect();
            }

            let res = connection.query(
                statement,
                values,
                function (error, results, fields) {
                    event.returnValue = {
                        status: error ? "error" : "success",
                        message: error ? error.message : "",
                        error,
                        fields,
                        results,
                    };
                }
            );

            //connection.end();
        }
        else {
            event.returnValue = {
                status: "error",
                message: "no connection",
                error: null,
                fields: null,
                results: null,
            };
        }

    }

    /**
     * 关闭数据库
     * @param event 
     * @param param1 
     */
    private mysqlClose(
        event: Event,
        { key = "" }: { key: string }
    ) {
        let connection = MysqlConn._connection_map.get(key);
        if (!_.isNil(connection)) {
            connection.end();
        }

    }
}

export default new MysqlConn();
